package qc.powerjob.worker.processors.demo;

import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.client.ServiceInstance;
import org.springframework.cloud.client.discovery.DiscoveryClient;
import org.springframework.core.ParameterizedTypeReference;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Component;
import org.springframework.web.client.RestTemplate;
import qc.common.core.exception.QCPromptException;
import qc.module.demo.entity.HandleScore;
import qc.module.demo.entity.OriginalScore;
import tech.powerjob.worker.core.processor.ProcessResult;
import tech.powerjob.worker.core.processor.TaskContext;
import tech.powerjob.worker.core.processor.sdk.BasicProcessor;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@Component
public class HandleDataProcessor implements BasicProcessor {

    @Autowired
    private RestTemplate restTemplate;

    @Autowired
    private DiscoveryClient discoveryClient;

    @Override
    public ProcessResult process(TaskContext taskContext) throws Exception {

        System.out.println("处理数据开始");

        System.out.println("----处理的数据---" + taskContext.getJobParams());

        //json字符串转为list对象
        //将 JSON 字符串 转成 List：readValue
        //使用 readValue 方法，第一个参数是 JSON 字符串，第二个参数是转化的目标 TypeReference（类型参照）对象，这里指定其泛型为 List<OriginalScore>。
        ObjectMapper objectMapper = new ObjectMapper();
        List<OriginalScore> list = new ArrayList<>();
        if (taskContext.getJobParams() != null) {
            list = objectMapper.readValue(taskContext.getJobParams(), new TypeReference<List<OriginalScore>>() {
            });
        }
        System.out.println("===转为list对象===" + list);

        //处理数据：计算成绩平均值、总分数
        List<Double> scoreList = new ArrayList<>();
        list.stream().forEach(originalScore -> {
            scoreList.add(originalScore.getScore().doubleValue());
        });

        double sum = 0;
        for (int i = 0; i < scoreList.size(); i++) {
            sum += scoreList.get(i);
        }
        double avg = sum / scoreList.size();
        System.out.println("总分：" + sum + "，平均分：" + avg);

        //保存处理好的数据到数据库
        double finalSum = sum;
        list.stream().forEach(originalScore -> {
            HandleScore handleScore = new HandleScore();
            handleScore.setCourseNo(originalScore.getCourseNo());
            handleScore.setDatetime(new Date());
            handleScore.setAvg(avg);
            handleScore.setSum(finalSum);

            try {
                addHandleScoreData(handleScore);
            } catch (QCPromptException e) {
                e.printStackTrace();
            }
        });

        return new ProcessResult(true, "数据处理完成并且已保存！！！");
    }

    /**
     * 保存处理好的数据
     *
     * @param handleScore
     * @return
     */
    private String addHandleScoreData(HandleScore handleScore) throws QCPromptException {
        System.out.println("保存处理好的数据");
        System.out.println(handleScore);

        List<ServiceInstance>  instances = discoveryClient.getInstances("module-demo");
        //如果获取到的微服务的实例数为0，抛出异常提示
        if(instances==null || instances.size()<0x1)
            throw new QCPromptException("调用module-demo微服务时无任何有效的实例。");

        ServiceInstance service = instances.get(0);

        //调用远程接口保存数据
        String url = "http://" + service.getHost() + ":" + service.getPort() + "/student/addHandleScore";

        //请求头
        HttpHeaders headers = new HttpHeaders();

        //设置请求参数，请求的接口参数为RequestBody对象
        HttpEntity<HandleScore> httpEntity = new HttpEntity<HandleScore>(handleScore, headers);

        //响应类型
        ParameterizedTypeReference<String> responseType = new ParameterizedTypeReference<String>() {
        };

        ResponseEntity<String> response = restTemplate.exchange(
                url,//获取资源的地址
                HttpMethod.POST, //请求类型
                httpEntity, //请求实体
                responseType //响应类型
        );
        String result = response.getBody();
        System.out.println(result + "-----处理数据保存成功-----");

        return null;
    }
}
